Header file index.hpp

namespace type_safe
{
    struct difference_t;
    
    struct index_t;
    
    constexpr index_t operator+(const index_t& lhs, const difference_t& rhs) noexcept;
    constexpr index_t operator+(const difference_t& lhs, const index_t& rhs) noexcept;
    
    constexpr index_t operator-(const index_t& lhs, const difference_t& rhs) noexcept;
    
    constexpr difference_t operator-(const index_t& lhs, const index_t& rhs) noexcept;
    
    template <typename Indexable>
    decltype(std::forward<Indexable>(obj)[static_cast<std::size_t>(get(index))]) at(Indexable&& obj, const index_t& index);
    
    void advance(index_t& index, const difference_t& dist);
    
    constexpr difference_t distance(const index_t& a, const index_t& b);
    
    constexpr index_t next(const index_t& index, const difference_t& dist = difference_t(1));
    
    constexpr index_t prev(const index_t& index, const difference_t& dist = difference_t(1));
}

Struct type_safe::difference_t [types]

struct difference_t
: strong_typedef<struct type_safe::difference_t, ptrdiff_t>,
  strong_typedef_op::equality_comparison<difference_t>,
  strong_typedef_op::relational_comparison<difference_t>,
  strong_typedef_op::unary_plus<difference_t>,
  strong_typedef_op::unary_minus<difference_t>,
  strong_typedef_op::addition<difference_t>,
  strong_typedef_op::subtraction<difference_t>
{
    constexpr difference_t() noexcept;
    
    template <typename T>
    constexpr difference_t(T i) noexcept;
    template <typename T, class Policy, typename = typename std::enable_if<detail::is_safe_integer_conversion<T, std::ptrdiff_t>::value>::type>
    constexpr difference_t(integer<T, Policy> i) noexcept;
};

A type modelling the difference between two ts::index_t objects.

It is a ts::strong_typedef for ts::ptrdiff_t. It is comparable and you can add and subtract two differences.

Default constructor type_safe::difference_t::difference_t

constexpr difference_t() noexcept;

Effects: Initializes it to 0.

Function template type_safe::difference_t::difference_t

(1)  template <typename T>
     constexpr difference_t(T i) noexcept;

(2)  template <typename T, class Policy, typename = typename std::enable_if<detail::is_safe_integer_conversion<T, std::ptrdiff_t>::value>::type>
     constexpr difference_t(integer<T, Policy> i) noexcept;

Effects: Initializes it from a valid signed integer type.

Notes: This constructor does not participate in overload resolution, if T is not safely convertible to ts::ptrdiff_t.


Struct type_safe::index_t [types]

struct index_t
: strong_typedef<struct type_safe::index_t, size_t>,
  strong_typedef_op::equality_comparison<index_t>,
  strong_typedef_op::relational_comparison<index_t>,
  strong_typedef_op::increment<index_t>,
  strong_typedef_op::decrement<index_t>,
  strong_typedef_op::unary_plus<index_t>
{
    constexpr index_t() noexcept;
    
    template <typename T>
    constexpr index_t(T i) noexcept;
    template <typename T, class Policy, typename = typename std::enable_if<detail::is_safe_integer_conversion<T, std::size_t>::value>::type>
    constexpr index_t(integer<T, Policy> i) noexcept;
    
    index_t& operator+=(const difference_t& rhs) noexcept;
    
    index_t& operator-=(const difference_t& rhs) noexcept;
};

A type modelling an index into an array.

It is a ts::strong_typedef for ts::size_t. It is comparable and you can increment and decrement it, as well as adding/subtracting a ts::distance_t.

Notes: It has a similar interface to a RandomAccessIterator, but without the dereference functions.

Default constructor type_safe::index_t::index_t

constexpr index_t() noexcept;

Effects: Initializes it to 0.

Function template type_safe::index_t::index_t

(1)  template <typename T>
     constexpr index_t(T i) noexcept;

(2)  template <typename T, class Policy, typename = typename std::enable_if<detail::is_safe_integer_conversion<T, std::size_t>::value>::type>
     constexpr index_t(integer<T, Policy> i) noexcept;

Effects: Initializes it from a valid unsigned integer type.

Notes: This constructor does not participate in overload resolution, if T is not safely convertible to ts::size_t.

Operator type_safe::index_t::operator+=

index_t& operator+=(const difference_t& rhs) noexcept;

Effects: Advances the index by the distance specified in rhs. If rhs is a negative distance, it advances backwards.

Requires: The new index must be greater or equal to 0.

Operator type_safe::index_t::operator-=

index_t& operator-=(const difference_t& rhs) noexcept;

Effects: Advances the index backwards by the distance specified in rhs. If rhs is a negative distance, it advances forwards.

Requires: The new index must be greater or equal to 0.


Operator type_safe::operator+ [types]

(1)  constexpr index_t operator+(const index_t& lhs, const difference_t& rhs) noexcept;

(2)  constexpr index_t operator+(const difference_t& lhs, const index_t& rhs) noexcept;

Returns: The given ts::index_t advanced by the given ts::distance_t.

Operator type_safe::operator- [types]

constexpr index_t operator-(const index_t& lhs, const difference_t& rhs) noexcept;

Returns: The given ts::index_t advanced backwards by the given ts::distance_t.

Operator type_safe::operator- [types]

constexpr difference_t operator-(const index_t& lhs, const index_t& rhs) noexcept;

Returns: Returns the distance between two indices. This is the number of steps you need to increment lhs to reach rhs, it is negative if lhs > rhs.

Function template type_safe::at

template <typename Indexable>
decltype(std::forward<Indexable>(obj)[static_cast<std::size_t>(get(index))]) at(Indexable&& obj, const index_t& index);

Returns: The ith element of obj by invoking its operator[] with the ts::index_t converted to std::size_t. \requires index must be a valid index for obj, i.e. less than the size of obj. \exclude return \module types

Function type_safe::advance [types]

void advance(index_t& index, const difference_t& dist);

Effects: Increments the ts::index_t by the specified distance. If the distance is negative, decrements the index instead.

Notes: This is the same as index += dist and the equivalent of std::advance().

Function type_safe::distance [types]

constexpr difference_t distance(const index_t& a, const index_t& b);

Returns: The distance between two ts::index_t objects, i.e. how often you'd have to increment a to reach b.

Notes: This is the same as b - a and the equivalent of std::distance().

Function type_safe::next [types]

constexpr index_t next(const index_t& index, const difference_t& dist = difference_t(1));

Returns: The ts::index_t that is dist greater than index.

Notes: This is the same as index + dist and the equivalent of std::next().

Function type_safe::prev [types]

constexpr index_t prev(const index_t& index, const difference_t& dist = difference_t(1));

Returns: The ts::index_t that is dist smaller than index.

Notes: This is the same as index - dist and the equivalent of std::prev().